Questo sito utilizza cookies solo per scopi di autenticazione sul sito e nient'altro. Nessuna informazione personale viene tracciata. Leggi l'informativa sui cookies.
seguendo parecchi tutorial in giro per il web, sono riuscito a realizzare una dll per la gestione della comunicazione ethernet tcp/ip, in questa ho implementato sia lato server, sia lato client.
Il mio problema è questo:
Possibile che io riesca ad inviare solamente circa 100messaggi al secondo tramite ethernet? (ogni messaggio è composto circa da 100byte).
I 2 pc interessati sono in rete ad 1gb (cavo e hub apposito)...
Avete qualche idea?
Ho provato anche a ridimensionare i buffer di lettura e scrittura in qualsiasi modo... ma niente... non cambia di una virgola.
Help !
Edit del 23/02/2011
Dopo un mese di test ho scoperto la causa, dovevo semplicemente impostare il time base, senza questo, quando si riechiede uno sleep di 1ms, il sistema operativo (non essendo real time) fa una pausetta caffè di 15ms!
Ora invio e ricevo circa 8000 parametri al secondo (stringhe al secondo)
Ultima modifica effettuata da Neo1986 il 23/02/2011 alle 9:07
la banda teorica di una 1Gbit è di 1024 / 8 = 128 MB/sec = 131072 KB/sec = 134217728 Byte/sec
ipotizzando una banda di 3/4 a causa di latenze varie e perdita dei cavi/switch/etc.. è cmq molto di più di quanto hai rilevato.
sicuramente il problema sta nella gestione di questi pacchetti, c'è troppo overhead di gestione o lato client o lato server.
mostra il codice e partiamo da lì.
allora, non hai specificato cosa contiene la variabile DaScrivere, da queste righe posso dedurre che è del testo:
Codice sorgente - presumibilmente C# / VB.NET
data = System.Text.Encoding.ASCII.GetString(bytes, 0, i)
_DaLeggere += data
i = stream.Read(bytes, 0, bytes.Length)
'pausa per far lavorare gli altri thread
Threading.Thread.Sleep(1)
questi dati provengono presumibilmente da un file, giusto?
avrai da qualche parte ReadAllText di un file di testo molto grosso.
Ipotizzando tutto questo ti assicuro che non è il metodo migliore quello che stai adottando, il primo punto è su _DaLeggere += data.
il clr deve istanziare un nuovo oggetto stringa e copiarci dentro tutto il nuovo contenuto AD OGNI iterazione, è una pessima cosa per le performances e la memoria utilizzata.
Ad ogni modo è proprio tutto l'approcio è che inefficiente, il modo migliore per inviare una qualsiasi ingente mole di dati attraverso socket è appoggiarsi al metodo CopyTo della classe Stream. Mi spiego meglio.
Se vuoi inviare un file attraverso socket, la cosa migliore da fare è aprire uno stream verso il file SENZA leggerne il contenuto esplicitamente e chiamare una CopyTo sul networkstream. In una riga:
per ricevere i dati crei uno stream in uscita verso il file che vuoi scrivere e di volta in volta ci scrivi dentro tutto il contenuto del networkstream:
Codice sorgente - presumibilmente VB.NET
Dim stream As NetworkStream = client.GetStream()
Dim writer As StreamWriter =File.OpenWrite("ciao.txt")
' Va dentro un ciclo
If stream.DataAvailableThen
stream.CopyTo(writer)
EndIf
in linea di massima è sempre meglio far gestire il buffering al CLR piuttosto che provarci a mano, si elimina un layer di overhead.
Ok, allora penso di aver capito in parte quello che mi stai dicendo, però forse non ho detto tutto...
Quelle 3 sub sono contenute in una dll, la variabile : DaScrivere, è come hai detto tu una proprietà string esposta dalla dll.
Non voglio assolutamente che mi scrivi tu il codice, ma...
Come potrei fare per inviare dall'esterno, del testo alla dll in modo più efficente di quello che ho fatto io?
Praticamente vorrei utilizzare questa dll in diversi programmi, magari inviare l'intero contenuto di un file di testo, oppure semplicemente passare una frase alla variabile DaScrivere (come il mio caso attuale)....
In sostanza non capisco come fare quello che hai detto:
il clr deve istanziare un nuovo oggetto stringa e copiarci dentro tutto il nuovo contenuto AD OGNI iterazione, è una pessima cosa per le performances e la memoria utilizzata.
Ok, allora penso di aver capito in parte quello che mi stai dicendo, però forse non ho detto tutto...
Quelle 3 sub sono contenute in una dll, la variabile : DaScrivere, è come hai detto tu una proprietà string esposta dalla dll.
Non voglio assolutamente che mi scrivi tu il codice, ma...
Come potrei fare per inviare dall'esterno, del testo alla dll in modo più efficente di quello che ho fatto io?
Praticamente vorrei utilizzare questa dll in diversi programmi, magari inviare l'intero contenuto di un file di testo, oppure semplicemente passare una frase alla variabile DaScrivere (come il mio caso attuale)....
In sostanza non capisco come fare quello che hai detto:
il clr deve istanziare un nuovo oggetto stringa e copiarci dentro tutto il nuovo contenuto AD OGNI iterazione, è una pessima cosa per le performances e la memoria utilizzata.
se si inviano files ci vogliono procedure adatte ed ottimizzate per l'invio di files, se si inviano brevi frasi di testo ci vuole altro, se si inviano immagini ci vuole altro ancora, etc...
per ogni cosa c'è la sua procedura più o meno ottimizzata ma specifica per l'implementazione, cosa che tu, facendo così, ti perdi.
ad ogni modo se proprio proprio devi passare per una variabile che contiene il testo da inviare, puoi usare il memorystream:
Codice sorgente - presumibilmente C# / VB.NET
MemoryStream stream = new MemoryStream(Encoding.Default.GetBytes(DaInviare));
stream.CopyTo(client.GetStream());
Ciao! era un problema di sleep del thread, non di overhead, impostando il timebase del sistema operativo a 1, tutto va al suo posto - Neo1986 - 23/02/11 09:09